// // /*
// //  * @Author: szx
// //  * @Date: 2022-03-10 15:31:41
// //  * @LastEditTime: 2022-03-10 16:58:36
// //  * @Description:
// //  * @FilePath: \MDN_JS学习\手撸JS源码\Promise.js
// //  */

// // // 正常的Promise是长这样子的
// // // var p = new Promise(function (resolve, reject) {
// // //     console.log('执行');
// // //     setTimeout(function () {
// // //         resolve(2);
// // //     }, 1000);
// // // });
// // // p.then(
// // //     function (res) {
// // //         console.log('suc', res);
// // //     },
// // //     function (err) {
// // //         console.log('err', err);
// // //     }
// // // );

// const PENDING = 'pending';
// const FULFILLED = 'fulfilled';
// const REJECTED = 'rejected';

// function _Promise(executor) {
//     const self = this;
//     self.state = PENDING; //状态
//     self.result = null;

//     self.callbacks = []; //保存回调函数

//     // resolve 为处理成功后调用的函数，并不是其中包括验证对象状态修改和次数修改，修改Promise实例对象状态
//     function resolve(value) {
//         // 只有当且仅当为pending的情况下，状态才能变化
//         if (self.state === PENDING) {
//             self.state = FULFILLED;
//             self.result = value;
//             // question，这里需要setTimeout吗？
//             setTimeout(() => {
//                 console.log('为啥会执行两次')
//                 self.callbacks.forEach((ele) => {
//                     ele.onFulfilled(value);
//                 });
//             });
//         }
//     }
//     function reject(reason) {
//         if (self.state === PENDING) {
//             self.state = REJECTED;
//             self.result = reason;
//             setTimeout(() => {
//                 self.callbacks.forEach((ele) => {
//                     ele.onRejected(reason);
//                 });
//             });
//         }
//     }

//     // Promise构造函数会立马执行函数
//     try {
//         executor(resolve, reject);
//     } catch (e) {
//         reject(e);
//     }
// }

// // 实例方法 then，有两个参数函数，分别是成功和失败的回调函数
// _Promise.prototype.then = function (onFulfilled, onRejected) {
//     if (typeof onFulfilled !== 'function') {
//         onFulfilled = (value) => value;
//     }
//     if (typeof onRejected !== 'function') {
//         onRejected = (reason) => {
//             throw reason;
//         };
//     }
//     const self = this;
//     return new _Promise((resolve, reject) => {
//         // 注意，这里面的this这个新创建的_Promise，而不是外面那个_self那个_Promise！
//         function handle(callback) {
//             try {
//                 // 但这里会获取外面_self的那个结果，然后执行callback函数
//                 let result = callback(self.result);
//                 // console.log('什么,', result);
//                 if (result instanceof _Promise) {
//                     result.then(
//                         (v) => resolve(v),
//                         (r) => reject(r)
//                     );
//                 } else {
//                     resolve(result);
//                 }
//             } catch (err) {
//                 reject(err);
//             }
//         }
//         if (self.state === PENDING) {
//             self.callbacks.push({
//                 onFulfilled(value) {
//                     handle(onFulfilled);
//                 },
//                 onRejected(reason) {
//                     handle(onRejected);
//                 }
//             });
//         }
//         if (self.state === FULFILLED) {
//             setTimeout(() => {
//                 handle(() => {
//                     onFulfilled;
//                 });
//             });
//         }
//         if (this.state === REJECTED) {
//             setTimeout(() => {
//                 handle(onRejected);
//             });
//         }
//     });
// };

// // 实例方法catch
// _Promise.prototype.catch = function (onRejected) {
//     return this.then(undefined, onRejected);
// };

// // 静态方法
// _Promise.resolve = function (value) {
//     return new _Promise((resolve, reject) => {
//         // 如果是Promise类型的，那么就转换成异步的
//         if (value instanceof _Promise) {
//             value.then(
//                 (v) => resolve(v),
//                 (r) => reject(r)
//             );
//         } else {
//             resolve(value);
//         }
//     });
// };

// _Promise.reject = function (reason) {
//     return new _Promise((resolve, reject) => {
//         reject(reason);
//     });
// };

// // new _Promise((resolve, reject) => {
// //     setTimeout(() => {
// //         console.log('1');
// //         resolve(1000);
// //         // return 1000;
// //     }, 1000);
// // })
// //     .then((res) => {
// //         console.log('2', res);
// //         return res;
// //     })
// //     .then((res) => {
// //         console.log('3', res + 1);
// //         throw res + 1;
// //     })
// //     .catch((err) => {
// //         console.log('err,', err);
// //     });

// var p = new _Promise(function (resolve, reject) {
//     console.log('执行');
//     resolve(3);
//     //     setTimeout(function () {
//     //         resolve(2);
//     //     }, 2000);
// });
// // console.log(p);
// p.then(
//     function (res) {
//         console.log('suc', res);
//         return 3;
//     },
//     function (err) {
//         console.log('err', err);
//     }
// );
// //     .then((res) => {
// //         console.log(res);
// //         // throw 4;
// //     })
// //     .catch((err) => {
// //         console.log(err);
// //     });

// // let promise = new _Promise((resolve, reject) => {
// //     setTimeout(() => {
// //         // 异步的
// //         resolve('value1'); // 此时调用resolve就让刚才存储成功的函数 去执行！可以认为then 时一个订阅 这俩方法是一个发布
// //     }, 1000); // 如果调用了resolve 就让刚才储存的成功的回调去执行！
// //     resolve('value2');
// //     //  throw new Error('我失败了')
// //     //  reject('reson')
// // });
// // // // 同一个peomise 可以then 多次！
// // promise.then(
// //     (success) => {
// //         // 如果调用then 时没有成功也没有失败，我们可以保存成功和失败的回调！
// //         console.log('success1', success);
// //     },
// //     (err) => {
// //         console.log('fail1', err);
// //     }
// // );
// // promise.then(
// //     (success) => {
// //         console.log('success2', success);
// //     },
// //     (err) => {
// //         console.log('fail2', err);
// //     }
// // );
